// ============================== 导入依赖 ============================== //

import CORE from '../UTIL'
import util from './util'

const InfoParamClass = {}
const InfoClass = {}

// ============================== 状态集 ============================== //

const state = {
  // —————————————————————————————— 数据 —————————————————————————————— //

  /**
   * 接口
   */
  API: {
    ...util.API,
    validInfoParam(infoParam, state, root) {
      return true
    },
    transInfoParam(infoParam, context) {
      return infoParam
    },
    async getInfo(infoParam, TIP) {
      throw util.errorAPI(TIP, 'getInfo')
    },
    transInfo(obj, context) {
      return obj
    },
  },

  /**
   * 映射
   */
  MAP: {
    WORD: '', // 词语 (初始常量，不可更新)

    GET: null, // 获取 (为 null 取 CORE.MAP.TIP_XXX，可设置为 '')
    INFO: null, // 信息 (为 null 取 CORE.MAP.TIP_XXX，可设置为 '')

    tipInfo: '', // 信息提示 (有值时直接使用，无值时拼接生成)
  },

  /**
   * 字典
   */
  DICT: {
    //
  },

  /**
   * 初始配置
   */
  INIT_CONFIG: {
    /**
     * 销毁前是否保持信息参数不变
     *
     * true  保留参数
     * false 重置参数 (将 INIT_INFO_PARAM 合并到 infoParam)
     */
    DESTROY_KEEP_INFO_PARAM: false,
  },

  /**
   * 初始信息参数
   *
   * 1. 初始存在，才能响应
   * 2. CORE.mixStore(store) 时使用
   * 3. setInfoParam() 重置时使用
   */
  INIT_INFO_PARAM: CORE.initObj(InfoParamClass, {
    //
  }),

  /**
   * 初始信息
   *
   * 1. 初始存在，才能响应
   * 2. setInfo() 合并时使用
   */
  INIT_INFO: CORE.initObj(InfoClass, {
    //
  }),

  /**
   * 信息参数
   */
  infoParam: {},

  /**
   * 信息
   */
  info: {},

  // —————————————————————————————— 弹窗 —————————————————————————————— //

  /**
   * 信息弹窗
   */
  infoVisible: false,

  /**
   * 信息类型
   */
  infoType: '',

  // —————————————————————————————— 开关 —————————————————————————————— //

  /**
   * 远程信息开关
   */
  needInfo: false,

  /**
   * 信息就绪开关
   */
  readyInfo: false,
}

// ============================== 计算属性 ============================== //

const getters = {}

// ============================== 同步更新 ============================== //

const mutations = {
  // —————————————————————————————— 设置 —————————————————————————————— //

  /**
   * 设置信息参数
   */
  setInfoParam(state, infoParam) {
    util.setClone(state, infoParam, 'infoParam')
  },

  /**
   * 设置信息
   */
  setInfo(state, info) {
    util.setClone(state, info, 'info')
  },

  // —————————————————————————————— 弹窗 —————————————————————————————— //

  /**
   * 设置信息类型
   */
  setInfoType(state, infoType) {
    state.infoType = infoType || ''
  },

  /**
   * 打开信息弹窗
   */
  openInfo(state, infoType) {
    state.infoVisible = true
    if (infoType) state.infoType = infoType
  },

  /**
   * 打开新信息的弹窗
   */
  openNewInfo(state, info) {
    if (CORE.isJSON(info)) util.setClone(state, info, 'info')
    state.infoType = 'pre_info' // 更新预设类型
    util.start('Info', state)
  },

  /**
   * 关闭信息弹窗
   */
  closeInfo(state) {
    state.infoVisible = false
  },

  // —————————————————————————————— 监听 —————————————————————————————— //

  /**
   * 开始远程信息
   */
  startInfo(state, infoParam) {
    const isObj = CORE.isJSON(infoParam)
    if (state.API.validInfoParam(isObj ? infoParam : state.infoParam, state, this)) {
      if (isObj) util.setClone(state, infoParam, 'infoParam') // 更新信息参数
      util.start('Info', state)
    } else {
      util.setClone(state, {}, 'info')
    }
  },

  /**
   * 完成远程信息
   */
  completeInfo(state, data) {
    let msgSuccess = ''
    if (CORE.isArray(data)) {
      if (CORE.isJSON(data[0])) util.setClone(state, data[0], 'info') // 设置信息
      if (CORE.isString(data[1])) msgSuccess = data[1] // 成功消息
    } else {
      if (CORE.isJSON(data)) util.setClone(state, data, 'info') // 设置信息
      if (CORE.isString(data)) msgSuccess = data // 成功消息
    }
    util.complete('Info', state, msgSuccess)

    // 检查 openNewInfo 弹窗
    if (state.infoType === 'pre_info') {
      state.infoType = '' // 恢复正常类型
      state.infoVisible = true // 更新可见
    }
  },

  /**
   * 终止远程信息
   */
  stopInfo(state, e) {
    util.stop('Info', state, e)
  },
}

// ============================== 异步调用 ============================== //

const actions = {
  // —————————————————————————————— 信息 —————————————————————————————— //

  async remoteInfo(context) {
    const { state: { API, MAP, infoParam } } = context
    const TIP = API.transTip(MAP.tipInfo, this.state.API) // 拼上根模块 API 的菜单

    const myParam = await API.transInfoParam(infoParam, context)

    const obj = await API.getInfo(myParam, TIP)

    return API.transInfo(obj, context)
  },
}

// ============================== 导出仓库 ============================== //

export default { state, getters, mutations, actions }
